package com.ccl.iot.views;

import android.content.Context;
import android.graphics.Bitmap;
import android.graphics.Color;
import android.graphics.Rect;
import android.view.MotionEvent;
import android.view.View;
import android.widget.ImageView;

import com.ccl.iot.R;
import com.ccl.iot.privates.BitmapBuilder;
import com.ccl.iot.template.StandardView;

public abstract class ItemView<TYPE> extends StandardView {
    public interface OnItemCheckChangeListener<TYPE> {
        public boolean onItemCheckChange(ItemView<TYPE> aItem, boolean aChecked);
    }

    private static Bitmap iCheckOnBitmap = null;
    private static Bitmap iCheckOffBitmap = null;

    private boolean iChecked = false;
    private ImageView iCheckBox = null;

    protected TYPE iItem = null;

    public ItemView(Context context, TYPE aItem) {
        super(context);

        iItem = aItem;

        this.setBackgroundColor(Color.TRANSPARENT);

        this.setFocusable(true);

        initialize();
    }

    private void initialize() {
        if (iCheckOnBitmap == null) {
            iCheckOnBitmap = BitmapBuilder.GetBitmap(this.getContext(), R.drawable.icon_checkbox_selected);
        }

        if (iCheckOffBitmap == null) {
            iCheckOffBitmap = BitmapBuilder.GetBitmap(this.getContext(), R.drawable.icon_checkbox_normal);
        }
    }

    public void setItem(TYPE aItem) {
        if (aItem != iItem) {
            iItem = aItem;

            this.postInvalidate();
        }
    }

    public TYPE getItem() {
        return iItem;
    }

    public void setCheckable(boolean aCheckable) {
        if (aCheckable) {
            if (iCheckBox == null) {
                iCheckBox = new ImageView(this.getContext());
                iCheckBox.setImageBitmap(iCheckOffBitmap);
                this.addView(iCheckBox);

                handleCheckBoxEvent();
            }
        } else {
            if (iCheckBox != null) {
                this.removeView(iCheckBox);

                iCheckBox = null;
            }

            iChecked = false;
        }
    }

    private OnItemCheckChangeListener<TYPE> iCheckChangeListener = null;

    public void setOnItemCheckChangeListener(OnItemCheckChangeListener<TYPE> aListener) {
        iCheckChangeListener = aListener;
    }

    public boolean isChecked() {
        return iChecked;
    }

    public void setChecked(boolean aChecked) {
        if (iCheckBox != null) {
            if (iCheckChangeListener != null) {
                if (iCheckChangeListener.onItemCheckChange(this, aChecked) == false) {
                    return;
                }
            }

            iChecked = aChecked;

            iCheckBox.setImageBitmap(iChecked ? iCheckOnBitmap : iCheckOffBitmap);
        }
    }

    private void handleCheckBoxEvent() {
        if (iCheckBox != null) {
            iCheckBox.setOnClickListener(new View.OnClickListener() {
                @Override
                public void onClick(View v) {
                    setChecked(!iChecked);
                }
            });
        }
    }

    private View.OnTouchListener iOnTouchListener = null;

    @Override
    public void setOnTouchListener(OnTouchListener aListener) {
        iOnTouchListener = aListener;
    }

    @Override
    public boolean onTouchEvent(MotionEvent event) {
        if (iOnTouchListener != null) {
            iOnTouchListener.onTouch(this, event);
        }
        return super.onTouchEvent(event);
    }

    @Override
    protected void onLayout(boolean changed, int l, int t, int r, int b) {
        //super.onLayout(changed, l, t, r, b);

        if (iCheckBox != null) {
            int tWidth = r - l;
            int tBitmapWidth = (iChecked ? iCheckOnBitmap.getWidth() : iCheckOffBitmap.getWidth());
            int tBitmapHeight = (iChecked ? iCheckOnBitmap.getHeight() : iCheckOffBitmap.getHeight());

            if (tBitmapWidth < (tWidth >> 2)) {
                tBitmapWidth = (int) (tBitmapWidth * 1.6f);
                tBitmapHeight = (int) (tBitmapHeight * 1.6f);
            }

            iCheckBox.layout(tWidth - tBitmapWidth, 0, tWidth, tBitmapHeight);
        }
    }

    protected abstract Rect calcRect();

    @Override
    protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
        int tWidthMode = MeasureSpec.getMode(widthMeasureSpec);
        int tHeightMode = MeasureSpec.getMode(heightMeasureSpec);
        int tWidth = 0, tHeight = 0;
        Rect tRect = calcRect();

        if (tWidthMode == MeasureSpec.UNSPECIFIED) {
            if (tRect != null) {
                tWidth = tRect.width();
            }
        } else {
            tWidth = MeasureSpec.getSize(widthMeasureSpec);

            if (tRect != null && tWidthMode == MeasureSpec.AT_MOST) {
                if (tRect.width() > 0 && tRect.width() < tWidth) {
                    tWidth = tRect.width();
                }
            }
        }

        if (tHeightMode == MeasureSpec.UNSPECIFIED) {
            if (tRect != null) {
                tHeight = tRect.height();
            }
        } else {
            tHeight = MeasureSpec.getSize(heightMeasureSpec);

            if (tRect != null && tHeightMode == MeasureSpec.AT_MOST) {
                if (tRect.height() > 0 && tRect.height() < tHeight) {
                    tHeight = tRect.height();
                }
            }
        }

        super.setMeasuredDimension(tWidth, tHeight);
    }

    protected void onShow() {

    }

    protected void onHide() {

    }

    private boolean iShowing = false;

    public boolean isShowing() {
        return iShowing;
    }

    private void afterWindowStateChange() {
        if (this.getHandler() != null && this.getWindowVisibility() == View.VISIBLE && this.getVisibility() == View.VISIBLE) {
            if (iShowing == false) {
                iShowing = true;

                onShow();
            }
        } else {
            if (iShowing) {
                iShowing = false;

                onHide();
            }
        }
    }

    @Override
    protected void onVisibilityChanged(View changedView, int visibility) {
        super.onVisibilityChanged(changedView, visibility);

        afterWindowStateChange();
    }

    @Override
    protected void onWindowVisibilityChanged(int visibility) {
        super.onWindowVisibilityChanged(visibility);

        afterWindowStateChange();
    }

    @Override
    protected void onAttachedToWindow() {
        super.onAttachedToWindow();

        afterWindowStateChange();
    }

    @Override
    protected void onDetachedFromWindow() {
        super.onDetachedFromWindow();

        afterWindowStateChange();
    }

    //=============modify start=============
    protected WaitRegView waitView = null;
    public void setWaitView(WaitRegView w){
        waitView = w;
    }
    //=============modify end=============
}
